#include "unp.h"

void
print_ip_port(const struct sockaddr *addr, socklen_t len) {
	char	buf[INET_ADDRSTRLEN+1];
	struct sockaddr_in	*addr_in = (struct sockaddr_in *)addr;

	if(inet_ntop(AF_INET, &addr_in->sin_addr, buf, INET_ADDRSTRLEN) != NULL) {
		perror("inet_ntop");
		exit(-1);
	}
	printf("%s:%d", buf, htons(addr_in->sin_port));
}

void
dg_cli(FILE *fp, int sockfd, struct sockaddr *pservaddr, socklen_t servlen) {
	int			n;
	char		sendline[MAXLINE], recvline[MAXLINE+1];
	socklen_t		len;
	struct sockaddr	*preply_addr;
	
	while(fgets(sendline, MAXLINE, fp) != NULL) {
		if (sendto(sockfd, sendline, strlen(sendline), 0, pservaddr, servlen) != strlen(sendline)) {
			perror("sendto");
			exit(-1);
		}
		n = recvfrom(sockfd, recvline, MAXLINE, 0, preply_addr, &len);
		if (len != servlen || memcmp(pservaddr, preply_addr, len) != 0) {
			printf("reply from "), print_ip_port(preply_addr, len), printf(" (ignored)\n");
			continue;
		}
		recvline[n] = 0;
		fputs(recvline, stdout);
	}
}

int
main(int argc, char *argv[]) {
	int					sockfd;
	struct sockaddr_in	servaddr;

	if (argc != 2) {
		printf("usage: %s <IP address>\n", argv[0]);
		exit(-1);
	}

	bzero(&servaddr, sizeof(servaddr));
	servaddr.sin_family = AF_INET;
	servaddr.sin_port = htons(7);
	if (inet_pton(AF_INET, argv[1], &servaddr.sin_addr) < 1) {
		perror("inet_pton");
		exit(-1);
	}

	if ((sockfd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
		perror("inet_pton");
		exit(-1);
	}

	dg_cli(stdin, sockfd, (struct sockaddr *)&servaddr, sizeof(servaddr));

	exit(0);
}
